package org.hitchhike.common.web.controller;

import java.io.Serializable;

import javax.validation.Valid;

import org.hitchhike.common.Constants;
import org.hitchhike.common.service.BaseService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.ui.Model;
import org.springframework.validation.BindingResult;
import org.springframework.web.bind.annotation.ModelAttribute;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.servlet.mvc.support.RedirectAttributes;

public abstract class BaseCRUDController<T, ID extends Serializable> extends BaseController<T, ID> {

  protected BaseService<T, ID> baseService;

  private boolean listAlsoSetCommonData = false;


  /**
   * 设置基础service
   *
   * @param baseService
   */
  @Autowired
  public void setBaseService(BaseService<T, ID> baseService) {
    this.baseService = baseService;
  }

  /**
   * 列表也设置common data
   */
  public void setListAlsoSetCommonData(boolean listAlsoSetCommonData) {
    this.listAlsoSetCommonData = listAlsoSetCommonData;
  }



  @RequestMapping(value = "/{id}", method = RequestMethod.GET)
  public String view(Model model, @PathVariable("id") T t) {

    setCommonData(model);
    model.addAttribute("t", t);
    model.addAttribute(Constants.OP_NAME, "查看");
    return viewName("editForm");
  }

  @RequestMapping(value = "create", method = RequestMethod.GET)
  public String showCreateForm(Model model) {

    setCommonData(model);
    model.addAttribute(Constants.OP_NAME, "新增");
    if (!model.containsAttribute("m")) {
      model.addAttribute("m", newModel());
    }
    return viewName("editForm");
  }


  @RequestMapping(value = "create", method = RequestMethod.POST)
  public String create(Model model, @Valid @ModelAttribute("t") T t, BindingResult result,
      RedirectAttributes redirectAttributes) {

    if (hasError(t, result)) {
      return showCreateForm(model);
    }
    baseService.save(t);
    redirectAttributes.addFlashAttribute(Constants.MESSAGE, "新增成功");
    return redirectToUrl(null);
  }


  @RequestMapping(value = "{id}/update", method = RequestMethod.GET)
  public String showUpdateForm(@PathVariable("id") T t, Model model) {

    setCommonData(model);
    model.addAttribute(Constants.OP_NAME, "修改");
    model.addAttribute("t", t);
    return viewName("editForm");
  }

  @RequestMapping(value = "{id}/update", method = RequestMethod.POST)
  public String update(Model model, @Valid @ModelAttribute("t") T t, BindingResult result,
      @RequestParam(value = Constants.BACK_URL, required = false) String backURL,
      RedirectAttributes redirectAttributes) {

    if (hasError(t, result)) {
      return showUpdateForm(t, model);
    }
    baseService.update(t);
    redirectAttributes.addFlashAttribute(Constants.MESSAGE, "修改成功");
    return redirectToUrl(backURL);
  }

  @RequestMapping(value = "{id}/delete", method = RequestMethod.GET)
  public String showDeleteForm(@PathVariable("id") T t, Model model) {

    setCommonData(model);
    model.addAttribute(Constants.OP_NAME, "删除");
    model.addAttribute("t", t);
    return viewName("editForm");
  }

  @RequestMapping(value = "{id}/delete", method = RequestMethod.POST)
  public String delete(@PathVariable("id") T t,
      @RequestParam(value = Constants.BACK_URL, required = false) String backURL,
      RedirectAttributes redirectAttributes) {

    baseService.delete(t);

    redirectAttributes.addFlashAttribute(Constants.MESSAGE, "删除成功");
    return redirectToUrl(backURL);
  }

  @RequestMapping(value = "batch/delete", method = {RequestMethod.GET, RequestMethod.POST})
  public String deleteInBatch(@RequestParam(value = "ids", required = false) ID[] ids,
      @RequestParam(value = Constants.BACK_URL, required = false) String backURL,
      RedirectAttributes redirectAttributes) {


    redirectAttributes.addFlashAttribute(Constants.MESSAGE, "删除成功");
    return redirectToUrl(backURL);
  }

}
